import 'dart:convert';
import 'dart:io';
import 'dart:typed_data';
import 'package:flutter/foundation.dart';
import 'package:csv/csv.dart';
import 'package:excel/excel.dart';
import 'package:file_selector/file_selector.dart';
import 'package:path_provider/path_provider.dart';
import 'package:permission_handler/permission_handler.dart';
import 'package:share_plus/share_plus.dart';
import '../models/word.dart';
import '../utils/encoding_util.dart';

class WordImportResult {
  final List<Word> words;
  final List<String> errors;
  final bool hasErrors;

  WordImportResult(this.words, this.errors) : hasErrors = errors.isNotEmpty;
}

class WordImportExportUtil {
  // 导出单词到CSV文件
  static Future<String?> exportWordsToCSV(List<Word> words) async {
    return _exportToCSV(words, exportType: 'word');
  }
  
  // 导出题目到CSV文件
  static Future<String?> exportQuestionsToCSV(List<dynamic> questions) async {
    // 在导出前验证每个题目的类型，但保留原始图片路径用于导出
    for (var i = 0; i < questions.length; i++) {
      var question = questions[i];
      String type = question['type'] ?? '';
      if (!_isValidQuestionType(type)) {
        print('警告: 第${i+1}个题目的类型"$type"无效，将使用默认类型"logical_reasoning"');
        question['type'] = 'logical_reasoning';
      }
      
      // 确保所有图片路径字段存在，但导出时保留原始路径
      if (!question.containsKey('question_image_url')) {
        question['question_image_url'] = '';
      } else {
        // 导出时保留原始图片路径，不进行validateImagePath处理
        question['question_image_url'] = question['question_image_url'] ?? '';
      }
      
      if (!question.containsKey('option_a_image_url')) {
        question['option_a_image_url'] = '';
      } else {
        question['option_a_image_url'] = question['option_a_image_url'] ?? '';
      }
      
      if (!question.containsKey('option_b_image_url')) {
        question['option_b_image_url'] = '';
      } else {
        question['option_b_image_url'] = question['option_b_image_url'] ?? '';
      }
      
      if (!question.containsKey('option_c_image_url')) {
        question['option_c_image_url'] = '';
      } else {
        question['option_c_image_url'] = question['option_c_image_url'] ?? '';
      }
      
      if (!question.containsKey('option_d_image_url')) {
        question['option_d_image_url'] = '';
      } else {
        question['option_d_image_url'] = question['option_d_image_url'] ?? '';
      }
      
      if (!question.containsKey('explanation_image_url')) {
        question['explanation_image_url'] = '';
      } else {
        question['explanation_image_url'] = question['explanation_image_url'] ?? '';
      }
      
      // 兼容旧版本
      if (!question.containsKey('imagePath')) {
        question['imagePath'] = '';
      }
    }
    return _exportToCSV(questions, exportType: 'question');
  }
  
  // 通用导出方法
  static Future<String?> _exportToCSV(List<dynamic> items, {required String exportType}) async {
    try {
      // 创建CSV数据
      List<List<dynamic>> csvData = [];
      
      // 根据导出类型添加不同的标题行和数据
      if (exportType == 'word') {
        // 单词导出格式
        csvData.add(['读音', '单词', '释义', '例句', '分类']);
        
        // 添加单词数据
        for (var word in items as List<Word>) {
          csvData.add([
            word.pronunciation ?? '',
            word.word,
            word.meaning ?? '',
            word.example ?? '',
            word.category ?? '',
          ]);
        }
      } else if (exportType == 'question') {
        // 题目导出格式
        csvData.add(['类型', '分类', '考点', '题目内容', '题目图片', '选项A', '选项A图片', '选项B', '选项B图片', '选项C', '选项C图片', '选项D', '选项D图片', '正确答案', '解析', '解析图片']);
        
        // 添加题目数据 - 这里假设items是包含题目信息的Map列表
        for (var question in items) {
          // 确保图片路径字段存在且不为null
          String questionImageUrl = (question['question_image_url'] ?? '').toString();
          String optionAImageUrl = (question['option_a_image_url'] ?? '').toString();
          String optionBImageUrl = (question['option_b_image_url'] ?? '').toString();
          String optionCImageUrl = (question['option_c_image_url'] ?? '').toString();
          String optionDImageUrl = (question['option_d_image_url'] ?? '').toString();
          String explanationImageUrl = (question['explanation_image_url'] ?? '').toString();
          
          // 打印所有图片路径，用于调试
          print('题目内容: ${question['content']}');
          print('题目图片路径: $questionImageUrl');
          print('选项A图片路径: $optionAImageUrl');
          print('选项B图片路径: $optionBImageUrl');
          print('选项C图片路径: $optionCImageUrl');
          print('选项D图片路径: $optionDImageUrl');
          print('解析图片路径: $explanationImageUrl');
          
          // 如果有图片路径，特别标注
          if (questionImageUrl.isNotEmpty) {
            print('✓ 导出包含题目图片: $questionImageUrl');
          }
          if (optionAImageUrl.isNotEmpty) {
            print('✓ 导出包含选项A图片: $optionAImageUrl');
          }
          if (optionBImageUrl.isNotEmpty) {
            print('✓ 导出包含选项B图片: $optionBImageUrl');
          }
          if (optionCImageUrl.isNotEmpty) {
            print('✓ 导出包含选项C图片: $optionCImageUrl');
          }
          if (optionDImageUrl.isNotEmpty) {
            print('✓ 导出包含选项D图片: $optionDImageUrl');
          }
          if (explanationImageUrl.isNotEmpty) {
            print('✓ 导出包含解析图片: $explanationImageUrl');
          }
          
          csvData.add([
            question['type'] ?? '',
            question['category'] ?? '',
            question['point'] ?? '',
            question['content'] ?? '',
            questionImageUrl,
            question['option_a'] ?? '',
            optionAImageUrl,
            question['option_b'] ?? '',
            optionBImageUrl,
            question['option_c'] ?? '',
            optionCImageUrl,
            question['option_d'] ?? '',
            optionDImageUrl,
            question['correct_answer'] ?? '',
            question['explanation'] ?? '',
            explanationImageUrl,
          ]);
        }
      }

      // 转换为CSV字符串
      String csv = const ListToCsvConverter().convert(csvData);

      // 根据导出类型确定文件名前缀和目录
      String filePrefix = exportType == 'word' ? '单词导出' : '题目导出';
      
      // 根据导出类型确定模块名称
      String moduleName = '';
      if (exportType == 'word') {
        moduleName = '词汇';
      } else if (exportType == 'question') {
        // 对于题目，根据第一个题目的类型确定模块名称
        if (items.isNotEmpty) {
          var firstQuestion = items[0];
          String type = firstQuestion['type'] ?? 'common_sense';
          
          // 根据题目类型确定模块名称
          switch (type) {
            case 'logical_reasoning':
              moduleName = '逻辑推理';
              break;
            case 'quantitative_relation':
              moduleName = '数量关系';
              break;
            case 'politics':
              moduleName = '时政';
              break;
            case 'common_sense':
              moduleName = '常识';
              break;
            case 'verbal_comprehension':
              moduleName = '言语理解';
              break;
            case 'data_analysis':
              moduleName = '资料分析';
              break;
            default:
              moduleName = '题库';
              break;
          }
        } else {
          moduleName = '题库';
        }
      }
      
      // 根据平台确定导出路径
      String dirPath;
      if (Platform.isWindows || Platform.isMacOS || Platform.isLinux) {
        // 桌面平台使用固定路径
        dirPath = 'D:\\000\\my-web\\学习宝库\\$moduleName';
        
        // 确保目录存在
        final directory = Directory(dirPath);
        if (!await directory.exists()) {
          await directory.create(recursive: true);
        }
        
        // 使用指定的目录路径
        final path = '$dirPath\\${filePrefix}_${DateTime.now().millisecondsSinceEpoch}.csv';
        final file = File(path);
        
        // 写入文件 - 使用带BOM的UTF-8编码，解决中文乱码问题
        List<int> bomUtf8 = [0xEF, 0xBB, 0xBF];
        List<int> csvBytes = utf8.encode(csv);
        List<int> bytesWithBom = [...bomUtf8, ...csvBytes];
        await file.writeAsBytes(bytesWithBom);
        
        print('文件已导出到: $path');
        return path;
      } else {
        // 移动平台使用Download/考试宝目录
        try {
          // 请求存储权限
          var status = await Permission.storage.request();
          if (!status.isGranted) {
            throw Exception('需要存储权限才能导出文件');
          }
          
          // 获取外部存储目录
          final directory = await getExternalStorageDirectory();
          if (directory == null) {
            throw Exception('无法获取外部存储目录');
          }
          
          // 获取Download目录 - 内部存储
          final downloadDir = Directory('${directory.path.split('Android')[0]}Download/学习宝库/$moduleName');
          print('导出类型: $exportType, 模块名称: $moduleName');
          dirPath = downloadDir.path;
          
          // 确保目录存在
          if (!await downloadDir.exists()) {
            await downloadDir.create(recursive: true);
          }
          
          // 使用指定的目录路径
          final path = '$dirPath/${filePrefix}_${DateTime.now().millisecondsSinceEpoch}.csv';
          final file = File(path);
          
          // 写入文件 - 使用带BOM的UTF-8编码，解决中文乱码问题
          List<int> bomUtf8 = [0xEF, 0xBB, 0xBF];
          List<int> csvBytes = utf8.encode(csv);
          List<int> bytesWithBom = [...bomUtf8, ...csvBytes];
          await file.writeAsBytes(bytesWithBom);
          
          print('移动平台导出路径: $path');
          return path;
        } catch (e) {
          print('设置移动平台导出路径失败: $e');
          throw Exception('设置导出路径失败: $e');
        }
      }

      // 代码不会执行到这里，因为所有分支都已经返回结果
      throw Exception('导出过程出现未知错误');
    } catch (e) {
      print('导出单词失败: $e');
      throw Exception('导出失败: $e');
    }
  }

  // 从CSV或Excel文件导入单词 - 超级宽松版本
  static Future<WordImportResult> importWordsFromCSVOrExcel() async {
    try {
      // 选择并读取CSV或Excel文件
      final fileResult = await _selectAndReadFile();
      final dataTable = fileResult.data;
      final detectedDelimiter = fileResult.delimiter;
      
      print('检测到的分隔符: "$detectedDelimiter"');
      
      // 验证表头
      if (dataTable.isEmpty) {
        throw Exception('文件为空');
      }
      
      // 获取表头
      final headers = dataTable[0];
      
      // 打印表头信息用于调试
      print('表头: ${headers.join(" | ")}');
      
      // 超级宽松模式：尝试识别表头字段
      Map<String, int> columnMap = _identifyColumns(headers);
      
      // 打印列映射结果
      columnMap.forEach((field, index) {
        print('字段 "$field" 映射到列索引: $index');
      });
      
      // 跳过标题行，解析数据行
      List<Word> importedWords = [];
      List<String> errors = [];
      
      for (int i = 1; i < dataTable.length; i++) {
        try {
          final row = dataTable[i];
          
          // 检查行是否为空或全部为空值
          if (row.isEmpty || row.every((cell) => cell == null || cell.toString().trim().isEmpty)) {
            continue; // 跳过空行
          }
          
          // 获取单词字段 - 必须有值
          String word = _getFieldValue(row, columnMap, 'word');
          if (word.isEmpty) {
            errors.add('第${i+1}行：单词不能为空');
            continue;
          }
          
          // 获取其他字段 - 可以为空
          String pronunciation = _getFieldValue(row, columnMap, 'pronunciation');
          String? meaning = _getNullableFieldValue(row, columnMap, 'meaning');
          String? example = _getNullableFieldValue(row, columnMap, 'example');
          String? category = _getNullableFieldValue(row, columnMap, 'category');
          
          importedWords.add(Word(
            pronunciation: pronunciation,
            word: word,
            meaning: meaning,
            example: example,
            category: category,
          ));
        } catch (rowError) {
          errors.add('第${i+1}行：解析错误 - $rowError');
        }
      }

      // 记录所有错误
      if (errors.isNotEmpty) {
        print('导入单词时发现以下问题：\n${errors.join('\n')}');
        if (importedWords.isEmpty) {
          // 如果没有成功导入任何单词，则抛出异常
          throw Exception('导入失败：\n${errors.join('\n')}');
        } else {
          // 如果有成功导入的单词，但也有错误，返回成功导入的单词，同时附加错误信息
          print('部分单词导入成功，共导入 ${importedWords.length} 个单词，但有 ${errors.length} 个错误');
        }
      } else {
        print('成功导入 ${importedWords.length} 个单词');
      }

      return WordImportResult(importedWords, errors);
    } catch (e) {
      print('导入单词失败: $e');
      rethrow;
    }
  }
  
  // 从CSV或Excel文件导入题目 - 超级宽松版本
  static Future<List<Map<String, dynamic>>> importQuestionsFromCSVOrExcel() async {
    try {
      // 选择并读取CSV或Excel文件
      final fileResult = await _selectAndReadFile();
      final dataTable = fileResult.data;
      
      // 打印数据表格信息用于调试
      print('选择的文件已加载');
      
      // 打印原始数据表格的前几行用于调试
      print('数据表格行数: ${dataTable.length}');
      if (dataTable.length > 1) {
        print('第1行数据(表头): ${dataTable[0]}');
        print('第2行数据(第1条记录): ${dataTable[1]}');
      }
       
       // 验证表头
      if (dataTable.isEmpty) {
        throw Exception('文件为空');
      }
      
      // 打印原始数据表格的前几行用于调试
       print('数据表格行数: ${dataTable.length}');
       if (dataTable.length > 1) {
         print('第1行数据(表头): ${dataTable[0]}');
         print('第2行数据(第1条记录): ${dataTable[1]}');
       }
      
      // 获取表头
      final headers = dataTable[0];
      
      // 打印表头信息用于调试
      print('表头: ${headers.join(" | ")}');
      
      // 检查表头是否与导出格式一致
      final expectedHeaders = ['类型', '分类', '考点', '题目内容', '题目图片', '选项A', '选项A图片', '选项B', '选项B图片', '选项C', '选项C图片', '选项D', '选项D图片', '正确答案', '解析', '解析图片'];
      final simplifiedHeaders = ['类型', '分类', '考点', '题目内容', '选项A', '选项B', '选项C', '选项D', '正确答案', '解析'];
      
      print('检查表头格式:');
      if (headers.length == expectedHeaders.length) {
        print('表头完整，包含图片字段');
      } else if (headers.length == simplifiedHeaders.length) {
        print('表头简化版，不包含图片字段');
      } else {
        print('表头格式不标准，将尝试智能匹配');
      }
      
      // 超级宽松模式：尝试识别题目表头字段
      Map<String, int> columnMap = identifyQuestionColumns(headers);
      
      // 打印列映射结果
      print('\n列映射结果:');
      columnMap.forEach((field, index) {
        print('字段 "$field" 映射到列索引: $index (${headers[index]})');
      });
      print('\n');
      
      // 跳过标题行，解析数据行
      List<Map<String, dynamic>> importedQuestions = [];
      
      for (int i = 1; i < dataTable.length; i++) {
        try {
          final row = dataTable[i];
          
          // 检查行是否为空或全部为空值
          if (row.isEmpty || row.every((cell) => cell == null || cell.toString().trim().isEmpty)) {
            continue; // 跳过空行
          }
          
          // 获取题目内容 - 必须有值
          print('正在处理第${i+1}行数据: ${row.join(", ")}');
          String content = _getFieldValue(row, columnMap, 'content');
          print('第${i+1}行题目内容: "$content"');
          
          // 检查题目内容是否有效（不仅仅是空，还要有实际内容）
          if (content.isEmpty || content == '1' || content.length < 2) {
            print('警告: 第${i+1}行题目内容无效或过短: "$content"，跳过');
            continue;
          }
          
          // 获取类型并确保它是有效的类型
          String type = _getFieldValue(row, columnMap, 'type');
          if (!_isValidQuestionType(type)) {
            print('警告: 第${i+1}行的题目类型"$type"无效，将使用默认类型"logical_reasoning"');
            type = 'logical_reasoning';
          }
          
          // 获取其他字段
          // 保留原始图片路径，不进行validateImagePath处理以避免本地路径丢失
          String safeGetImagePath(String fieldName) {
            // 先尝试通过columnMap获取
            String value = _getFieldValue(row, columnMap, fieldName);
            
            // 如果为空，尝试直接通过中文字段名获取
            if (value.isEmpty) {
              String chineseName = '';
              if (fieldName == 'question_image_url') chineseName = '题目图片';
              else if (fieldName == 'option_a_image_url') chineseName = '选项A图片';
              else if (fieldName == 'option_b_image_url') chineseName = '选项B图片';
              else if (fieldName == 'option_c_image_url') chineseName = '选项C图片';
              else if (fieldName == 'option_d_image_url') chineseName = '选项D图片';
              else if (fieldName == 'explanation_image_url') chineseName = '解析图片';
              
              if (chineseName.isNotEmpty) {
                // 查找表头中对应的中文字段索引
                int index = -1;
                for (int i = 0; i < headers.length; i++) {
                  if (headers[i].toString().trim() == chineseName) {
                    index = i;
                    break;
                  }
                }
                
                if (index >= 0 && index < row.length) {
                  value = row[index]?.toString().trim() ?? '';
                  print('通过中文字段名"$chineseName"(索引$index)直接获取图片路径: "$value"');
                  
                  // 检查获取的值是否为null字符串
                  if (value.toLowerCase() == 'null') {
                    print('通过中文字段名获取的值为"null"字符串，设为空');
                    value = '';
                  }
                  
                  // 检查文件是否存在
                  if (value.isNotEmpty) {
                    if (File(value).existsSync()) {
                      print('通过中文字段名获取的图片文件存在: "$value"');
                    } else {
                      print('通过中文字段名获取的图片文件不存在: "$value"');
                      // 尝试修复路径
                      if (value.contains('\\')) {
                        String fixedPath = value.replaceAll('\\\\', '\\');
                        print('尝试修复路径: "$fixedPath"');
                        if (File(fixedPath).existsSync()) {
                          print('修复后的路径存在: "$fixedPath"');
                          value = fixedPath;
                        }
                      }
                    }
                  }
                }
              }
            }
            
            print('获取图片字段 "$fieldName": "$value"'); // 调试信息
            return value; // 直接返回原始路径，不进行验证处理
          }
          
          Map<String, dynamic> questionMap = {
            'type': type,
            'category': _getFieldValue(row, columnMap, 'category'),
            'point': _getFieldValue(row, columnMap, 'point'),
            'content': content,
            'question_image_url': safeGetImagePath('question_image_url'),
            'option_a': _getFieldValue(row, columnMap, 'option_a'),
            'option_a_image_url': safeGetImagePath('option_a_image_url'),
            'option_b': _getFieldValue(row, columnMap, 'option_b'),
            'option_b_image_url': safeGetImagePath('option_b_image_url'),
            'option_c': _getFieldValue(row, columnMap, 'option_c'),
            'option_c_image_url': safeGetImagePath('option_c_image_url'),
            'option_d': _getFieldValue(row, columnMap, 'option_d'),
            'option_d_image_url': safeGetImagePath('option_d_image_url'),
            'correct_answer': _getFieldValue(row, columnMap, 'correct_answer'),
            'explanation': _getFieldValue(row, columnMap, 'explanation'),
            'explanation_image_url': safeGetImagePath('explanation_image_url'),
          };
          
          // 添加到导入题目列表
          importedQuestions.add(questionMap);
          
          // 打印导入的题目信息，用于调试
          print('成功导入第${i+1}行题目: ${content.substring(0, content.length > 30 ? 30 : content.length)}...');
          print('题目类型: $type');
          print('题目图片路径: ${safeGetImagePath('question_image_url')}');
          print('正确答案: ${_getFieldValue(row, columnMap, 'correct_answer')}');

        } catch (rowError) {
          print('警告: 第${i+1}行解析错误 - $rowError');
        }
      }

      print('成功导入 ${importedQuestions.length} 个题目');
      return importedQuestions;
    } catch (e) {
      print('导入题目失败: $e');
      rethrow;
    }
  }
  
  // 从行数据中获取字段值（非空）
  static String _getFieldValue(List<dynamic> row, Map<String, int> columnMap, String fieldName) {
    int index = columnMap[fieldName] ?? -1;
    print('_getFieldValue: 字段"$fieldName" -> 索引$index, 行长度${row.length}');
    
    // 特殊处理图片字段 - 直接检查原始表头名称
    if (fieldName.contains('image_url') && index == -1) {
      // 尝试直接通过中文名称查找
      String chineseName = '';
      if (fieldName == 'question_image_url') chineseName = '题目图片';
      else if (fieldName == 'option_a_image_url') chineseName = '选项A图片';
      else if (fieldName == 'option_b_image_url') chineseName = '选项B图片';
      else if (fieldName == 'option_c_image_url') chineseName = '选项C图片';
      else if (fieldName == 'option_d_image_url') chineseName = '选项D图片';
      else if (fieldName == 'explanation_image_url') chineseName = '解析图片';
      
      if (chineseName.isNotEmpty) {
        // 查找表头中是否有对应的中文名称
        for (int i = 0; i < row.length && i < 20; i++) { // 限制搜索范围
          if (i < row.length && row[0] != null && row[0].toString().trim() == chineseName) {
            print('_getFieldValue: 通过中文名称"$chineseName"找到图片字段，尝试使用索引$i');
            index = i;
            break;
          }
        }
      }
    }
    
    if (index >= 0 && index < row.length) {
      final value = row[index];
      if (value == null) {
        return ''; // 保持空值为空字符串
      }
      String stringValue = value.toString().trim();
      // 如果值是字符串"null"，转换为空字符串
      if (stringValue.toLowerCase() == 'null') {
        return '';
      }
      // 检查是否包含非法字符或编码问题
      if (stringValue.contains('�')) {
        // 尝试清理非法字符
        stringValue = stringValue.replaceAll('�', '');
      }
      // 如果是图片字段，检查路径是否存在
      if (fieldName.contains('image_url') && stringValue.isNotEmpty) {
        // 检查文件是否存在
        if (File(stringValue).existsSync()) {
          // 图片文件存在
        } else {
          // 尝试修复常见路径问题
          if (stringValue.contains('\\')) {
            // 尝试替换双反斜杠为单反斜杠
            String fixedPath = stringValue.replaceAll('\\\\', '\\');
            if (File(fixedPath).existsSync()) {
              stringValue = fixedPath;
            }
          }
        }
      }
      // 如果原始值为空字符串，保持为空，不要被其他值替代
      return stringValue;
    }
    return ''; // 如果列不存在，返回空字符串
  }
  
  // 从行数据中获取可空字段值
  static String? _getNullableFieldValue(List<dynamic> row, Map<String, int> columnMap, String fieldName) {
    String value = _getFieldValue(row, columnMap, fieldName);
    return value.isEmpty ? null : value;
  }
  
  // 识别单词CSV表头字段
  static Map<String, int> _identifyColumns(List<dynamic> headers) {
    Map<String, int> columnMap = {};
    
    // 定义字段匹配规则
    final fieldMatchers = {
      'pronunciation': [
        '读音', 'pronunciation', 'pinyin', 'sound', '拼音', '音标',
        // 可能的乱码匹配
        'du yin', 'duyin', 'ÁÒÒô', 'ÁÒÒô', 'ÁÒ', 'ÁÒ'
      ],
      'word': [
        '单词', 'word', 'term', 'vocabulary', '词汇', '词语', '词条',
        // 可能的乱码匹配
        'dan ci', 'danci', '´Ê', '´Ê', 'µ¥´Ê', 'µ¥´Ê'
      ],
      'meaning': [
        '释义', 'meaning', 'definition', 'translation', '翻译', '解释', '含义', '中文', '中文释义', '中文翻译',
        // 可能的乱码匹配
        'shi yi', 'shiyi', 'ÊÍÒ', 'ÊÍÒ', 'ÊÍÒå', 'ÊÍÒå'
      ],
      'example': [
        '例句', 'example', 'sentence', 'usage', '用法', '示例', '例子',
        // 可能的乱码匹配
        'li ju', 'liju', 'Àý¾ä', 'Àý¾ä', 'Àý', 'Àý'
      ],
      'category': [
        '分类', 'category', 'type', 'class', 'group', '类别', '类型', '标签', '标记',
        // 可能的乱码匹配
        'fen lei', 'fenlei', '·ÖÀà', '·ÖÀà', '·Ö', '·Ö'
      ],
    };
    
    // 检查每个表头字段
    for (int i = 0; i < headers.length; i++) {
      String headerStr = headers[i]?.toString().trim().toLowerCase() ?? '';
      
      // 跳过空表头
      if (headerStr.isEmpty) continue;
      
      // 尝试匹配每个字段
      bool matched = false;
      fieldMatchers.forEach((fieldName, matchers) {
        if (matched) return; // 如果已经匹配到，跳过后续匹配
        for (String matcher in matchers) {
          if (headerStr == matcher.toLowerCase() || 
              headerStr.contains(matcher.toLowerCase())) {
            columnMap[fieldName] = i;
            print('匹配到字段 "$fieldName" 在列 $i: "${headers[i]}"');
            matched = true;
            break;
          }
        }
      });
    }
    
    // 如果没有找到某些关键字段，使用默认列映射
    if (!columnMap.containsKey('word')) {
      // 如果没有找到单词字段，默认使用第二列（如果存在）
      if (headers.length > 1) {
        columnMap['word'] = 1;
        print('未找到单词字段，默认使用第2列: "${headers.length > 1 ? headers[1] : ''}"');
      } else if (headers.isNotEmpty) {
        // 如果只有一列，则使用第一列
        columnMap['word'] = 0;
        print('未找到单词字段，默认使用第1列: "${headers[0]}"');
      }
    }
    
    if (!columnMap.containsKey('pronunciation')) {
      // 如果没有找到读音字段，默认使用第一列（如果存在且不是单词列）
      if (headers.isNotEmpty && columnMap['word'] != 0) {
        columnMap['pronunciation'] = 0;
        print('未找到读音字段，默认使用第1列: "${headers[0]}"');
      }
    }
    
    // 为其他字段设置默认值（如果存在足够的列）
    if (!columnMap.containsKey('meaning') && headers.length > 2) {
      columnMap['meaning'] = 2;
      print('未找到释义字段，默认使用第3列: "${headers.length > 2 ? headers[2] : ''}"');
    }
    
    if (!columnMap.containsKey('example') && headers.length > 3) {
      columnMap['example'] = 3;
      print('未找到例句字段，默认使用第4列: "${headers.length > 3 ? headers[3] : ''}"');
    }
    
    if (!columnMap.containsKey('category') && headers.length > 4) {
      columnMap['category'] = 4;
      print('未找到分类字段，默认使用第5列: "${headers.length > 4 ? headers[4] : ''}"');
    }
    
    return columnMap;
  }
  
  // 识别题目CSV表头字段
  static Map<String, int> identifyQuestionColumns(List<dynamic> headers) {
    Map<String, int> columnMap = {};
    
    // 打印原始表头，用于调试
    print('原始表头: ${headers.join(" | ")}');
    
    // 检查表头是否为简化版（没有图片字段）
    bool isSimplifiedHeader = headers.length == 10 && 
                             !headers.any((h) => h.toString().toLowerCase().contains('图片'));
    
    if (isSimplifiedHeader) {
      print('检测到简化版表头（无图片字段），将调整字段映射策略');
    } else {
      print('检测到完整版表头或自定义表头，将尝试智能匹配');
    }
    
    // 定义字段匹配规则 - 按优先级排序，更具体的匹配放在前面
    final fieldMatchers = {
      // 图片字段优先匹配（更具体）
      'question_image_url': [
        '题目图片', '题目图片路径', 'question image', 'question image url', '题干图片',
      ],
      'option_a_image_url': [
        '选项A图片', '选项A图片路径', 'option A image', 'option A image url', 'A图片',
      ],
      'option_b_image_url': [
        '选项B图片', '选项B图片路径', 'option B image', 'option B image url', 'B图片',
      ],
      'option_c_image_url': [
        '选项C图片', '选项C图片路径', 'option C image', 'option C image url', 'C图片',
      ],
      'option_d_image_url': [
        '选项D图片', '选项D图片路径', 'option D image', 'option D image url', 'D图片',
      ],
      'explanation_image_url': [
        '解析图片', '解析图片路径', 'explanation image', 'explanation image url', '解析图',
      ],
      // 文本字段（较宽泛的匹配）
      'type': [
        '类型', 'type', 'question type', '题型', '题目类型',
      ],
      'category': [
        '分类', 'category', 'class', '类别', '题目分类',
      ],
      'point': [
        '考点', 'point', 'knowledge point', '知识点', '要点',
      ],
      'content': [
        '题目内容', '题目', 'content', 'question', 'question content', '内容', '题干',
      ],
      'option_a': [
        '选项A', 'option A', 'A', 'A选项', 'A项',
      ],
      'option_b': [
        '选项B', 'option B', 'B', 'B选项', 'B项',
      ],
      'option_c': [
        '选项C', 'option C', 'C', 'C选项', 'C项',
      ],
      'option_d': [
        '选项D', 'option D', 'D', 'D选项', 'D项',
      ],
      'correct_answer': [
        '正确答案', '答案', 'answer', 'correct answer', '正确选项',
      ],
      'explanation': [
        '解析', 'explanation', 'analysis', '题目解析', '答案解析', '详解',
      ],
    };
    
    // 检查每个表头字段
    for (int i = 0; i < headers.length; i++) {
      String headerStr = headers[i]?.toString().trim().toLowerCase() ?? '';
      
      // 跳过空表头
      if (headerStr.isEmpty) continue;
      
      // 尝试匹配每个字段
      bool matched = false;
      fieldMatchers.forEach((fieldName, matchers) {
        if (matched) return; // 如果已经匹配到，跳过后续匹配
        for (String matcher in matchers) {
          if (headerStr == matcher.toLowerCase() || 
              headerStr.contains(matcher.toLowerCase())) {
            columnMap[fieldName] = i;
            print('✓ 匹配到字段 "$fieldName" 在列 $i: "${headers[i]}" 通过模式 "$matcher"');
            matched = true;
            break;
          }
        }
      });
    }
    
    // 如果没有找到某些关键字段，使用默认列映射
    if (!columnMap.containsKey('content') && headers.length > 3) {
      columnMap['content'] = 3;
      print('未找到题目内容字段，默认使用第4列');
    }
    
    if (!columnMap.containsKey('type') && headers.isNotEmpty) {
      columnMap['type'] = 0;
      print('未找到类型字段，默认使用第1列');
    }
    
    // 使用之前检测的简化版表头标志
    if (isSimplifiedHeader) {
      print('使用简化版表头默认映射策略');
      // 简化版表头默认映射
      if (!columnMap.containsKey('category') && headers.length > 1) columnMap['category'] = 1;
      if (!columnMap.containsKey('point') && headers.length > 2) columnMap['point'] = 2;
      if (!columnMap.containsKey('option_a') && headers.length > 4) columnMap['option_a'] = 4;
      if (!columnMap.containsKey('option_b') && headers.length > 5) columnMap['option_b'] = 5;
      if (!columnMap.containsKey('option_c') && headers.length > 6) columnMap['option_c'] = 6;
      if (!columnMap.containsKey('option_d') && headers.length > 7) columnMap['option_d'] = 7;
      if (!columnMap.containsKey('correct_answer') && headers.length > 8) columnMap['correct_answer'] = 8;
      if (!columnMap.containsKey('explanation') && headers.length > 9) columnMap['explanation'] = 9;
    } else {
      print('检测到完整版表头或自定义表头，使用智能映射策略');
      // 如果是16列的标准格式，使用固定映射
      if (headers.length == 16) {
        print('检测到16列标准格式，使用固定映射');
        // 标准16列格式：类型,分类,考点,题目内容,题目图片,选项A,选项A图片,选项B,选项B图片,选项C,选项C图片,选项D,选项D图片,正确答案,解析,解析图片
        final standardMapping = {
          'type': 0,
          'category': 1,
          'point': 2,
          'content': 3,
          'question_image_url': 4,
          'option_a': 5,
          'option_a_image_url': 6,
          'option_b': 7,
          'option_b_image_url': 8,
          'option_c': 9,
          'option_c_image_url': 10,
          'option_d': 11,
          'option_d_image_url': 12,
          'correct_answer': 13,
          'explanation': 14,
          'explanation_image_url': 15,
        };
        
        // 只有在没有匹配到的字段才使用标准映射
        standardMapping.forEach((field, index) {
          if (!columnMap.containsKey(field)) {
            columnMap[field] = index;
            print('使用标准映射：字段 "$field" -> 列 $index');
          }
        });
      } else {
        // 为其他字段设置默认值（如果存在足够的列）
        int defaultIndex = 0;
        ['category', 'point', 'question_image_url', 'option_a', 'option_a_image_url', 
         'option_b', 'option_b_image_url', 'option_c', 'option_c_image_url', 
         'option_d', 'option_d_image_url', 'correct_answer', 'explanation', 'explanation_image_url'].forEach((field) {
          if (!columnMap.containsKey(field)) {
            defaultIndex++;
            if (defaultIndex < headers.length && defaultIndex != columnMap['content']) {
              columnMap[field] = defaultIndex;
              print('未找到$field字段，默认使用第${defaultIndex+1}列');
            }
          }
        });
      }
    }
    
    // 最终的列映射结果
    columnMap.forEach((field, index) {
      if (index < headers.length) {
        // 保留映射结果
      }
    });
    
    return columnMap;
  }
  
  // 验证题目类型是否有效
  static bool isValidQuestionType(String type) {
    // 预定义的有效题目类型列表
    final validTypes = [
      'logical_reasoning',  // 逻辑推理
      'quantitative_relation', // 数量关系
      'politics',           // 时政
      'common_sense',       // 常识
      'verbal_comprehension', // 言语理解
      'data_analysis'       // 资料分析
    ];
    
    return validTypes.contains(type);
  }
  
  // 为了向后兼容，保留私有方法
  static bool _isValidQuestionType(String type) {
    return isValidQuestionType(type);
  }
  
  // 验证图片路径是否有效
  static String validateImagePath(String? imagePath) {
    // 确保参数不为null或空
    if (imagePath == null || imagePath.isEmpty) {
      return ''; // 空值保持为空字符串，不转换为null
    }
    
    String trimmedPath = imagePath.trim();
    
    // 检查是否是本地文件路径
    bool isLocalFilePath = trimmedPath.startsWith('/') || 
                          RegExp(r'^[A-Za-z]:\\').hasMatch(trimmedPath) || 
                          trimmedPath.startsWith('c:/') || 
                          trimmedPath.startsWith('C:/') ||
                          trimmedPath.contains(':\\Users\\') ||
                          trimmedPath.contains(':/Users/') ||
                          trimmedPath.contains('/Users/') ||
                          trimmedPath.contains('/Documents/');
    
    if (isLocalFilePath) {
      // 本地文件路径需要转换为应用内资源路径或使用File API加载
      // 对于Flutter Web，本地文件路径无法直接访问，但在桌面应用中应该保留
      if (kIsWeb) {
        return ''; // 在Web平台上返回空字符串
      } else {
        // 在非Web平台上，检查文件是否存在
        try {
          final file = File(trimmedPath);
          if (file.existsSync()) {
            return trimmedPath; // 文件存在，返回原始路径
          } else {
            print('警告: 图片文件不存在: $trimmedPath');
            return ''; // 文件不存在，返回空字符串
          }
        } catch (e) {
          print('警告: 检查图片文件时出错: $e');
          return ''; // 发生错误，返回空字符串
        }
      }
    }
    
    // 检查URL格式
    if (!trimmedPath.startsWith('http://') && !trimmedPath.startsWith('https://')) {
      // 如果不是以http或https开头，直接添加https前缀
      trimmedPath = 'https://$trimmedPath';
    }
    
    // 检查URL是否包含域名
    if (trimmedPath.startsWith('http')) {
      try {
        final uri = Uri.parse(trimmedPath);
        if (uri.host.isEmpty) {
          return '';
        }
      } catch (e) {
        return '';
      }
    }
    
    return trimmedPath;
  }
  
  // 选择并读取CSV或Excel文件的通用方法 - 超级宽松版本，增强GBK支持
  static Future<FileReadResult> _selectAndReadFile() async {
    try {
      // 请求存储权限
      var status = await Permission.storage.request();
      if (!status.isGranted) {
        throw Exception('需要存储权限才能导入文件');
      }

      // 选择文件
      final typeGroup = XTypeGroup(
        label: '表格文件',
        extensions: ['csv', 'xls', 'xlsx'],
      );
      final XFile? result = await openFile(
        acceptedTypeGroups: [typeGroup],
      );

      if (result == null) {
        throw Exception('未选择文件');
      }

      // 读取文件内容
      final file = File(result.path);
      final filePath = result.path;
      
      // 检查文件扩展名
      final fileExt = filePath.split('.').last.toLowerCase();
      print('文件扩展名: $fileExt');
      
      // 确定文件类型
      final fileType = (fileExt == 'xls' || fileExt == 'xlsx') ? FileFormat.excel : FileFormat.csv;
      
      // 读取文件字节
      final Uint8List bytes = await file.readAsBytes();
      print('文件大小: ${bytes.length} 字节');
      
      // 如果是Excel文件，使用excel库解析
      if (fileType == FileFormat.excel) {
        try {
          print('检测到Excel文件，使用excel库解析');
          return await _parseExcelFile(bytes);
        } catch (e) {
          print('Excel解析失败: $e');
          print('尝试作为CSV文件解析...');
        }
      }
      
      // 检查文件头部字节
      if (bytes.length > 20) {
        print('文件头部20个字节: ${bytes.sublist(0, 20).map((b) => '0x${b.toRadixString(16).padLeft(2, "0")}').join(" ")}');
      }
      
      // 检查是否有BOM标记
      bool hasBom = bytes.length >= 3 && 
                    bytes[0] == 0xEF && 
                    bytes[1] == 0xBB && 
                    bytes[2] == 0xBF;
      print('文件${hasBom ? "有" : "没有"}BOM标记');
      
      // 去除BOM标记（如果存在）
      final Uint8List processedBytes = EncodingUtil.removeBomFromBytes(bytes);
      
      // 尝试检测文件编码
      bool isLikelyGBK = false;
      if (processedBytes.length > 10) {
        // 检查是否可能是GBK编码
        for (int i = 0; i < processedBytes.length - 1; i++) {
          int byte = processedBytes[i];
          if (byte >= 0x81 && byte <= 0xFE && i + 1 < processedBytes.length) {
            int secondByte = processedBytes[i + 1];
            if (secondByte >= 0x40 && secondByte <= 0xFE) {
              isLikelyGBK = true;
              print('检测到可能是GBK编码的文件');
              break;
            }
          }
        }
      }
      
      // 尝试使用不同编码解码内容
      String content;
      if (isLikelyGBK) {
        // 如果可能是GBK编码，直接使用我们的GBK解码方法
        try {
          content = EncodingUtil.decodeGBK(processedBytes);
          print('使用GBK编码成功解码文件内容');
        } catch (e) {
          print('GBK解码失败，尝试其他编码: $e');
          content = EncodingUtil.decodeBytes(processedBytes);
        }
      } else {
        // 否则使用常规解码方法
        content = EncodingUtil.decodeBytes(processedBytes);
      }
      print('成功读取文件内容');
      
      // 打印前100个字符用于调试
      if (content.length > 100) {
        print('文件内容前100个字符: ${content.substring(0, 100)}');
      } else {
        print('文件内容: $content');
      }
      
      // 检查内容中的特殊字符
      final specialChars = content.split('')
          .where((c) => c.codeUnitAt(0) > 127)
          .take(10)
          .map((c) => '${c}(0x${c.codeUnitAt(0).toRadixString(16)})')
          .join(', ');
      if (specialChars.isNotEmpty) {
        print('文件中包含的特殊字符示例: $specialChars');
      }
      
      // 自动检测分隔符
      String delimiter = _detectDelimiter(content);
      print('检测到的分隔符: "$delimiter"');
      
      // 解析CSV
      List<List<dynamic>> csvTable;
      try {
        // 尝试使用检测到的分隔符解析CSV
        csvTable = const CsvToListConverter(
          shouldParseNumbers: false, // 不自动解析数字
          allowInvalid: true, // 允许无效的CSV格式
        ).convert(content, fieldDelimiter: delimiter);
        
        // 处理CSV中的空值，确保空字段保持为null
        csvTable = csvTable.map((row) {
          return row.map((cell) {
            if (cell == null) {
              return null; // null值保持为null
            }
            String cellStr = cell.toString().trim();
            if (cellStr.isEmpty) {
              return null; // 空字符串转换为null
            }
            return cell; // 有值的字段保持原值
          }).toList();
        }).toList();
        
        print('CSV解析成功，共${csvTable.length}行');
        
        // 打印表头用于调试
        if (csvTable.isNotEmpty) {
          print('CSV表头: ${csvTable[0].join(" | ")}');
          
          // 打印第一行数据用于调试
          if (csvTable.length > 1) {
            print('第一行数据: ${csvTable[1].join(" | ")}');
          }
        }
      } catch (e) {
        print('使用分隔符 "$delimiter" 解析CSV失败: $e');
        // 尝试使用更简单的分割方法
        try {
          print('尝试使用简单分割方法解析CSV...');
          final lines = content.split(RegExp(r'\r\n|\r|\n'));
          csvTable = lines
              .where((line) => line.trim().isNotEmpty) // 过滤空行
              .map((line) => line.split(delimiter))
              .toList();
          
          // 处理简单分割中的空值
          csvTable = csvTable.map((row) {
            return row.map((cell) {
              if (cell == null) {
                return null; // null值保持为null
              }
              String cellStr = cell.toString().trim();
              if (cellStr.isEmpty) {
                return null; // 空字符串转换为null
              }
              return cell; // 有值的字段保持原值
            }).toList();
          }).toList();
          
          print('简单分割方法解析成功，共${csvTable.length}行');
          
          if (csvTable.isNotEmpty) {
            print('CSV表头(简单分割): ${csvTable[0].join(" | ")}');
          }
        } catch (e2) {
          print('简单分割方法也失败: $e2');
          // 最后尝试使用空格分割
          try {
            print('尝试使用空格分割...');
            final lines = content.split(RegExp(r'\r\n|\r|\n'));
            csvTable = lines
                .where((line) => line.trim().isNotEmpty) // 过滤空行
                .map((line) => line.split(RegExp(r'\s+')))
                .toList();
            
            // 处理空格分割中的空值
            csvTable = csvTable.map((row) {
              return row.map((cell) {
                if (cell == null) {
                  return null; // null值保持为null
                }
                String cellStr = cell.toString().trim();
                if (cellStr.isEmpty) {
                  return null; // 空字符串转换为null
                }
                return cell; // 有值的字段保持原值
              }).toList();
            }).toList();
            
            print('空格分割成功，共${csvTable.length}行');
            delimiter = ' ';
          } catch (e3) {
            print('所有解析方法都失败: $e3');
            throw Exception('文件格式错误，无法解析');
          }
        }
      }

      // 检查CSV格式
      if (csvTable.isEmpty) {
        throw Exception('解析后的数据为空');
      }
      
      // 如果是Excel文件但扩展名错误，尝试修复表格结构
      if (fileExt != 'csv' && _looksLikeExcel(csvTable)) {
        print('检测到可能是Excel格式，尝试修复表格结构');
        csvTable = _fixExcelTable(csvTable);
      }
      
      // 如果只有一列，尝试其他分隔符
      if (csvTable[0].length <= 1) {
        print('只检测到一列数据，尝试其他分隔符');
        final alternativeDelimiters = [',', ';', '\t', '|'];
        for (var altDelimiter in alternativeDelimiters) {
          if (altDelimiter == delimiter) continue;
          
          try {
            var altTable = const CsvToListConverter(
              shouldParseNumbers: false,
              allowInvalid: true,
            ).convert(content, fieldDelimiter: altDelimiter);
            
            if (altTable.isNotEmpty && altTable[0].length > 1) {
              print('使用分隔符 "$altDelimiter" 成功解析出多列数据');
              
              // 处理替代分隔符解析中的空值
              altTable = altTable.map((row) {
                return row.map((cell) {
                  if (cell == null) {
                    return null; // null值保持为null
                  }
                  String cellStr = cell.toString().trim();
                  if (cellStr.isEmpty) {
                    return null; // 空字符串转换为null
                  }
                  return cell; // 有值的字段保持原值
                }).toList();
              }).toList();
              
              csvTable = altTable;
              delimiter = altDelimiter;
              break;
            }
          } catch (e) {
            // 忽略错误，继续尝试下一个分隔符
          }
        }
      }
      
      return FileReadResult(csvTable, delimiter, FileFormat.csv);
    } catch (e) {
      print('读取文件失败: $e');
      rethrow;
    }
  }
  
  // 解析Excel文件
  static Future<FileReadResult> _parseExcelFile(Uint8List bytes) async {
    try {
      // 使用excel库解析Excel文件
      final excel = Excel.decodeBytes(bytes);
      
      // 获取第一个工作表
      if (excel.tables.isEmpty) {
        throw Exception('Excel文件没有工作表');
      }
      
      final sheet = excel.tables.keys.first;
      final table = excel.tables[sheet];
      
      if (table == null || table.rows.isEmpty) {
        throw Exception('Excel工作表为空');
      }
      
      print('Excel工作表名称: $sheet');
      print('Excel行数: ${table.rows.length}');
      
      // 转换为二维数组格式
      List<List<dynamic>> data = [];
      
      for (var row in table.rows) {
        List<dynamic> rowData = [];
        for (var cell in row) {
          // 保持空单元格为null，不转换为空字符串
          // 这样可以避免后续处理中空值被替代的问题
          var cellValue = cell?.value;
          if (cellValue == null || cellValue.toString().trim().isEmpty) {
            rowData.add(null); // 空单元格保持为null
          } else {
            rowData.add(cellValue.toString());
          }
        }
        data.add(rowData);
      }
      
      // 打印表头用于调试
      if (data.isNotEmpty) {
        print('Excel表头: ${data[0].join(" | ")}');
        
        // 打印第一行数据用于调试
        if (data.length > 1) {
          print('第一行数据: ${data[1].join(" | ")}');
        }
      }
      
      return FileReadResult(data, ',', FileFormat.excel);
    } catch (e) {
      print('解析Excel文件失败: $e');
      rethrow;
    }
  }
  
  // 检测CSV文件的分隔符
  static String _detectDelimiter(String content) {
    // 常见的分隔符
    final delimiters = [',', ';', '\t', '|'];
    Map<String, int> delimiterCounts = {};
    
    // 只检查前几行
    final lines = content.split(RegExp(r'\r\n|\r|\n')).take(5).toList();
    
    // 统计每种分隔符在每行中的出现次数
    for (var line in lines) {
      if (line.trim().isEmpty) continue;
      
      for (var delimiter in delimiters) {
        int count = line.split(delimiter).length - 1;
        delimiterCounts[delimiter] = (delimiterCounts[delimiter] ?? 0) + count;
      }
    }
    
    // 找出出现次数最多的分隔符
    String bestDelimiter = ',';
    int maxCount = 0;
    
    delimiterCounts.forEach((delimiter, count) {
      print('分隔符 "$delimiter" 出现 $count 次');
      if (count > maxCount) {
        maxCount = count;
        bestDelimiter = delimiter;
      }
    });
    
    // 如果没有找到明显的分隔符，默认使用逗号
    return maxCount > 0 ? bestDelimiter : ',';
  }
  
  // 检查是否看起来像Excel表格（单元格合并或格式问题）
  static bool _looksLikeExcel(List<List<dynamic>> table) {
    if (table.isEmpty) return false;
    
    // 检查行长度是否不一致
    int firstRowLength = table[0].length;
    bool hasInconsistentRows = table.any((row) => row.length != firstRowLength);
    
    // 检查是否有大量空单元格
    int totalCells = 0;
    int emptyCells = 0;
    for (var row in table) {
      for (var cell in row) {
        totalCells++;
        if (cell == null || cell.toString().trim().isEmpty) {
          emptyCells++;
        }
      }
    }
    double emptyRatio = totalCells > 0 ? emptyCells / totalCells : 0;
    
    return hasInconsistentRows || emptyRatio > 0.5;
  }
  
  // 修复Excel表格结构问题
  static List<List<dynamic>> _fixExcelTable(List<List<dynamic>> table) {
    if (table.isEmpty) return table;
    
    // 找出最大行长度
    int maxColumns = 0;
    for (var row in table) {
      if (row.length > maxColumns) {
        maxColumns = row.length;
      }
    }
    
    // 确保所有行都有相同的列数
    List<List<dynamic>> fixedTable = [];
    for (var row in table) {
      if (row.every((cell) => cell == null || cell.toString().trim().isEmpty)) {
        // 跳过完全空的行
        continue;
      }
      
      List<dynamic> fixedRow = List.filled(maxColumns, '');
      for (int i = 0; i < row.length; i++) {
        fixedRow[i] = row[i] ?? '';
      }
      fixedTable.add(fixedRow);
    }
    
    return fixedTable;
  }
}

// 文件类型枚举
enum FileFormat {
  csv,
  excel
}

// 文件读取结果类
class FileReadResult {
  final List<List<dynamic>> data;
  final String delimiter;
  final FileFormat fileType;
  
  FileReadResult(this.data, this.delimiter, this.fileType);
}